package com.xigege.netty.nettyComponent.channel;

import io.netty.bootstrap.Bootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelFutureListener;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioSocketChannel;
import io.netty.handler.codec.string.StringEncoder;

import java.net.InetSocketAddress;

public class ChannelFutureClient {
    public static void main(String[] args) throws InterruptedException {
        ChannelFuture channelFuture = new Bootstrap()
                .group(new NioEventLoopGroup(2))
                .channel(NioSocketChannel.class)
                .handler(new ChannelInitializer<NioSocketChannel>() {
                    @Override
                    protected void initChannel(NioSocketChannel ch) throws Exception {
                        ch.pipeline().addLast(new StringEncoder());
                    }
                })
                // 1. 连接到服务器
                // 异步非阻塞，
                // 异步：调用connect方法的main线程不关心结果，发起调用后，把命令交给另一个线程去干活（NioEventLoopGroup中的一个线程）
                // 非阻塞：去干活发起连接的是另一个线程，当前mian线程调用connect后，就继续往下运行不用等结果
                .connect(new InetSocketAddress("localhost", 6666));

        // 等待连接服务器时，可以使用2.1或2.2的操作来定义连接之后的操作

        // 2.1 同步等待建立连接，阻塞当前线程，直到nio线程建立连接完毕
        channelFuture.sync();
        // 获取到channel
        Channel channel = channelFuture.channel();
        System.out.println(Thread.currentThread().getName() + "执行任务！");
        channel.writeAndFlush("hehehe...");

        // 2.2 使用 addListener 方法异步处理结果，等待结果的也不是main线程
        // 把等待连接建立以及等待连接建立之后处理结果的活全部交给另外的线程
        // 只需要给一个回调，将来结果完成后执行什么样的操作
//        channelFuture.addListener(new ChannelFutureListener() {
//            @Override
//            // nio线程连接建立好之后，会调用 operationComplete
//            public void operationComplete(ChannelFuture future) throws Exception {
//                // 获取到channel
//                Channel channel = channelFuture.channel();
//                System.out.println(Thread.currentThread().getName() + "执行任务！");
//                channel.writeAndFlush("hehehe...");
//            }
//        });
    }
}
